package com.szt.sy.controller.system.menu;

import java.util.HashMap;
import java.util.List;
import java.util.Map;

import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.ResponseBody;
import org.springframework.web.servlet.ModelAndView;

import com.szt.sy.anontation.Authority;
import com.szt.sy.anontation.AuthorityConfig;
import com.szt.sy.anontation.SysLog;
import com.szt.sy.common.AuthorityCommon;
import com.szt.sy.controller.base.AdminBaseController;
import com.szt.sy.entity.system.Menu;
import com.szt.sy.service.system.menu.MenuService;
import com.szt.sy.util.json.JsonUtils;
import com.szt.sy.vo.rep.base.RepBaseVO;

/***
 * 菜单控制器
 * 
 * @author wwy
 *
 */
@Controller
@AuthorityConfig(prefix = "/admin/menu/listAllMenu")
@RequestMapping(value = "admin/menu")
public class MenuController extends AdminBaseController {
	
	@Autowired
	private MenuService menuService;
	
	/**
	 * 显示菜单列表
	 *
	 * @param model
	 * @return
	 */
	@Authority(name = AuthorityCommon.LIST)
	@RequestMapping
	public ModelAndView list(@RequestParam Map<String, Object> map) throws Exception {
		ModelAndView mv = this.getModelAndView();
		String menuId = (String) map.get("MENU_ID");
		if (StringUtils.isBlank(menuId)) {
			menuId = "0";
		}
		List<Menu> menuList = menuService.listSubMenuByParentId(Long.parseLong(menuId));
		// 传入父菜单所有信息
		mv.addObject("pd", menuService.getMenuById(Long.parseLong(menuId)));
		mv.addObject("MENU_ID", menuId);
		mv.addObject("MSG", StringUtils.defaultIfBlank((String) map.get("MSG"), "list"));
		mv.addObject("menuList", menuList);
		mv.setViewName("system/menu/menu_list");
		
		return mv;
	}
	
	/**
	 * 请求新增菜单页面
	 *
	 * @param model
	 * @return
	 */
	@Authority(name = AuthorityCommon.ADD)
	@RequestMapping(value = "/toAdd")
	public ModelAndView toAdd(@RequestParam Map<String, Object> map) throws Exception {
		ModelAndView mv = this.getModelAndView();
		String menuId = (String) map.get("MENU_ID");
		if (StringUtils.isBlank(menuId)) {
			menuId = "0";
		}
		// 传入父菜单所有信息
		mv.addObject("pds", menuService.getMenuById(Long.parseLong(menuId)));
		// 传入菜单ID，作为子菜单的父菜单ID用
		mv.addObject("id", menuId);
		// 执行状态 add 为添加
		mv.addObject("MSG", "add");
		mv.setViewName("system/menu/menu_edit");
		
		return mv;
	}
	
	/**
	 * 保存菜单信息
	 *
	 * @param menu
	 * @param model
	 * @return
	 */
	@SysLog("菜单-添加")
	@Authority(name = AuthorityCommon.ADD)
	@RequestMapping(value = "/add")
	public ModelAndView add(Menu menu) throws Exception {
		ModelAndView mv = this.getModelAndView();
		// 默认菜单图标
		menu.setMenuIcon("menu-icon fa fa-leaf black");
		// 保存菜单
		menuService.saveMenu(menu);
		// 保存成功跳转到列表页面
		mv.setViewName("redirect:/admin/menu?MSG='change'&MENU_ID=" + menu.getParentId());
		return mv;
	}
	
	/**
	 * 删除菜单
	 *
	 * @param MENU_ID
	 * @param out
	 */
	@SysLog("菜单-删除")
	@SuppressWarnings({ "rawtypes", "unchecked" })
	@Authority(name = AuthorityCommon.DELETE)
	@RequestMapping(value = "/delete")
	@ResponseBody
	public RepBaseVO delete(@RequestParam Long id) throws Exception {
		RepBaseVO repVO = new RepBaseVO<>();
		Map<String, String> map = new HashMap<>(1);
		String errInfo = "";
		// 判断是否有子菜单，是：不允许删除
		if (menuService.listSubMenuByParentId(id).size() > 0) {
			errInfo = "false";
		} else {
			menuService.deleteMenuById(id);
			errInfo = "success";
		}
		
		map.put("result", errInfo);
		return repVO.setCommonSuccess().setData(map);
	}
	
	/**
	 * 请求编辑菜单页面
	 *
	 * @param
	 * @return
	 */
	@Authority(name = AuthorityCommon.EDIT)
	@RequestMapping(value = "/toEdit")
	public ModelAndView toEdit(Long id) throws Exception {
		ModelAndView mv = this.getModelAndView();
		// 读取此ID的菜单数据
		Menu menu = menuService.getMenuById(id);
		// 放入视图容器
		mv.addObject("pd", menu);
		// 传入父菜单所有信息
		mv.addObject("pds", menuService.getMenuById(menu.getParentId()));
		// 传入父菜单ID，作为子菜单的父菜单ID用
		mv.addObject("MENU_ID", menu.getParentId());
		mv.addObject("MSG", "edit");
		// 按钮权限
		
		mv.setViewName("system/menu/menu_edit");
		
		return mv;
	}
	
	/**
	 * 保存编辑
	 *
	 * @param
	 * @return
	 */
	@SysLog("菜单-修改")
	@Authority(name = AuthorityCommon.EDIT)
	@RequestMapping(value = "/edit")
	public ModelAndView edit(Menu menu) throws Exception {
		ModelAndView mv = this.getModelAndView();
		menuService.edit(menu);
		// 保存成功跳转到列表页面
		mv.setViewName("redirect:/admin/menu?MSG='change'&MENU_ID=" + menu.getParentId());
		return mv;
	}
	
	/**
	 * 请求编辑菜单图标页面
	 *
	 * @param
	 * @return
	 */
	@Authority(name = AuthorityCommon.EDIT)
	@RequestMapping(value = "/toEditicon")
	public ModelAndView toEditicon(String id, @RequestParam Map<String, Object> map) throws Exception {
		ModelAndView mv = this.getModelAndView();
		map.put("id", id);
		mv.addObject("pd", map);
		mv.setViewName("system/menu/menu_icon");
		
		return mv;
	}
	
	/**
	 * 保存菜单图标
	 *
	 * @param
	 * @return
	 */
	@SysLog("菜单-图标修改")
	@Authority(name = AuthorityCommon.EDIT)
	@RequestMapping(value = "/editicon")
	public ModelAndView editicon(String id, String menuIcon) throws Exception {
		ModelAndView mv = this.getModelAndView();
		menuService.editicon(id, menuIcon);
		mv.addObject("msg", "success");
		
		mv.setViewName("save_result");
		return mv;
	}
	
	/**
	 * 显示菜单列表ztree(菜单管理)
	 *
	 * @param model
	 * @return
	 */
	@Authority(name = AuthorityCommon.LIST)
	@RequestMapping(value = "/listAllMenu")
	public ModelAndView listAllMenu(Model model, String id) throws Exception {
		ModelAndView mv = this.getModelAndView();
		
		String json = JsonUtils.beanToString(menuService.listAllMenu(Menu.ROOT_ID));
		json = json.replaceAll("id", "id").replaceAll("parentId", "pId").replaceAll("menuName", "name")
				.replaceAll("subMenu", "nodes").replaceAll("ownMenuRights", "checked").replaceAll("inMenuUrl", "url");
		model.addAttribute("zTreeNodes", json);
		mv.addObject("MENU_ID", id);
		mv.setViewName("system/menu/menu_ztree");
		return mv;
	}
	
	/**
	 * 显示菜单列表ztree(拓展左侧四级菜单)
	 *
	 * @param model
	 * @return
	 */
	@Authority(name = AuthorityCommon.LIST)
	@RequestMapping(value = "/otherlistMenu")
	public ModelAndView otherlistMenu(Model model, Long menuId) throws Exception {
		ModelAndView mv = this.getModelAndView();
		String menuUrl = menuService.getMenuById(menuId).getMenuUrl();
		if ("#".equals(menuUrl.trim()) || "".equals(menuUrl.trim()) || null == menuUrl) {
			menuUrl = "login_default";
		}
		// 获取本角色菜单权限
		String roleRights = StringUtils.defaultString(getLoginUser().getRole().getRights());
		// 获取某菜单下所有子菜单
		List<Menu> athmenuList = menuService.listAllMenu(menuId);
		// 根据权限分配菜单
		athmenuList = this.readMenu(athmenuList, roleRights);
		String json = JsonUtils.beanToString(athmenuList);
		json = json.replaceAll("id", "id").replaceAll("parentId", "pId").replaceAll("menuName", "name")
				.replaceAll("subMenu", "nodes").replaceAll("ownMenuRights", "checked").replaceAll("menuUrl", "url")
				.replaceAll("#", "");
		model.addAttribute("zTreeNodes", json);
		// 本ID菜单链接
		mv.addObject("MENU_URL", menuUrl);
		mv.setViewName("system/menu/menu_ztree_other");
		
		return mv;
	}
	
	/**
	 * 根据角色权限获取本权限的菜单列表(递归处理)
	 *
	 * @param menuList：传入的总菜单
	 * @param roleRights：加密的权限字符串
	 * @return
	 */
	public List<Menu> readMenu(List<Menu> menuList, String roleRights) {
		for (int i = 0; i < menuList.size(); i++) {
			menuList.get(i).setOwnMenuRights(true);
			// 判断是否有此菜单权限并且是否隐藏
			if (menuList.get(i).isOwnMenuRights() && "1".equals(menuList.get(i).getMenuState())) {
				// 是：继续排查其子菜单
				this.readMenu(menuList.get(i).getSubMenu(), roleRights);
			} else {
				menuList.remove(i);
				i--;
			}
		}
		return menuList;
	}
	
}
